<!-- HTML header for doxygen 1.8.13-->
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta http-equiv="Content-Type" content="text/xhtml;charset=UTF-8"/>
<meta http-equiv="X-UA-Compatible" content="IE=9"/>
<meta name="generator" content="Doxygen 1.8.13"/>
<meta name="viewport" content="width=device-width, initial-scale=1"/>
<title>MTB CAT1 Peripheral driver library: Prot         (Protection Unit)</title>
<link href="tabs.css" rel="stylesheet" type="text/css"/>
<script type="text/javascript" src="jquery.js"></script>
<script type="text/javascript" src="dynsections.js"></script>
<link href="navtree.css" rel="stylesheet" type="text/css"/>
<script type="text/javascript" src="resize.js"></script>
<script type="text/javascript" src="navtreedata.js"></script>
<script type="text/javascript" src="navtree.js"></script>
<script type="text/javascript">
  $(document).ready(initResizable);
</script>
<link href="search/search.css" rel="stylesheet" type="text/css"/>
<script type="text/javascript" src="search/searchdata.js"></script>
<script type="text/javascript" src="search/search.js"></script>
<link href="doxygen_style.css" rel="stylesheet" type="text/css" />
</head>
<body>
<div id="top"><!-- do not remove this div, it is closed by doxygen! -->
<div id="titlearea">
<table cellspacing="0" cellpadding="0">
 <tbody>
 <tr style="height: 56px;">
  <td id="projectlogo"><a href="http://www.cypress.com/"><img alt="Logo" src="IFXCYP_one-line.png"/></a></td>
  <td id="projectalign" style="padding-left: 0.5em;">
   <div id="projectname">MTB CAT1 Peripheral driver library</div>
  </td>
 </tr>
 </tbody>
</table>
</div>
<!-- end header part -->
<!-- Generated by Doxygen 1.8.13 -->
<script type="text/javascript">
var searchBox = new SearchBox("searchBox", "search",false,'Search');
</script>
<script type="text/javascript" src="menudata.js"></script>
<script type="text/javascript" src="menu.js"></script>
<script type="text/javascript">
$(function() {
  initMenu('',true,false,'search.php','Search');
  $(document).ready(function() { init_search(); });
});
</script>
<div id="main-nav"></div>
</div><!-- top -->
<div id="side-nav" class="ui-resizable side-nav-resizable">
  <div id="nav-tree">
    <div id="nav-tree-contents">
      <div id="nav-sync" class="sync"></div>
    </div>
  </div>
  <div id="splitbar" style="-moz-user-select:none;" 
       class="ui-resizable-handle">
  </div>
</div>
<script type="text/javascript">
$(document).ready(function(){initNavTree('group__group__prot.html','');});
</script>
<div id="doc-content">
<!-- window showing the filter options -->
<div id="MSearchSelectWindow"
     onmouseover="return searchBox.OnSearchSelectShow()"
     onmouseout="return searchBox.OnSearchSelectHide()"
     onkeydown="return searchBox.OnSearchSelectKey(event)">
</div>

<!-- iframe showing the search results (closed by default) -->
<div id="MSearchResultsWindow">
<iframe src="javascript:void(0)" frameborder="0" 
        name="MSearchResults" id="MSearchResults">
</iframe>
</div>

<div class="header">
  <div class="summary">
<a href="#groups">API Reference</a>  </div>
  <div class="headertitle">
<div class="title">Prot (Protection Unit)</div>  </div>
</div><!--header-->
<div class="contents">
<a name="details" id="details"></a><h2 class="groupheader">General Description</h2>
<p>The Protection Unit driver provides an API to configure the Memory Protection Units (MPU), Shared Memory Protection Units (SMPU), and Peripheral Protection Units (PPU). </p>
<p>These are separate from the ARM Core MPUs and provide additional mechanisms for securing resource accesses. The Protection units address the following concerns in an embedded design:</p><ul>
<li><b>Security requirements:</b> This includes the prevention of malicious attacks to access secure memory or peripherals.</li>
<li><b>Safety requirements:</b> This includes detection of accidental (non-malicious) SW errors and random HW errors. It is important to enable failure analysis to investigate the root cause of a safety violation.</li>
</ul>
<p>The functions and other declarations used in this driver are in cy_prot.h. You can include cy_pdl.h to get access to all functions and declarations in the PDL.</p>
<h1><a class="anchor" id="group_prot_protection_type"></a>
Protection Types</h1>
<p>Protection units are hardware configuration structures that control bus accesses to the resources that they protect. By combining these individual configuration structures, a system is built to allow strict restrictions on the capabilities of individual bus masters (e.g. CM0+, CM4, Crypt) and their operating modes. This architecture can then be integrated into the overall security system of the end application. To build this system, 3 main protection unit types are available; MPU, SMPU and PPU. When a resource is accessed (memory/register), it must pass the evaluation performed for each category. These access evaluations are prioritized, where MPU has the highest priority, followed by SMPU, followed by PPU. i.e. if an SMPU and a PPU protect the same resource and if access is denied by the SMPU, then the PPU access evaluation is skipped. This can lead to a denial-of-service scenario and the application should pay special attention in taking ownership of the protection unit configurations.</p>
<h2><a class="anchor" id="group_prot_memory_protection"></a>
Memory Protection</h2>
<p>Memory access control for a bus master is controlled using an MPU. These are most often used to distinguish user and privileged accesses from a single bus master such as task switching in an OS/kernel. For ARM cores (CM0+, CM4), the core MPUs are used to perform this task. For other non-ARM bus masters such as Crypto, MPU structs are available, which can be used in a similar manner as the ARM core MPUs. These MPUs however must be configured by the ARM cores. Other bus masters that do not have an MPU, such as DMA (DW), inherit the access control attributes of the bus master that configured the channel. Also note that unlike other protection units, MPUs do not support protection context evaluation. MPU structs have a descending priority, where larger index struct has higher priority access evaluation over lower index structs. E.g. MPU_STRUCT15 has higher priority than MPU_STRUCT14 and its access will be evaluated before MPU_STRUCT14. If both target the same memory, then the higher index (MPU_STRUCT15) will be used, and the lower index (MPU_STRUCT14) will be ignored.</p>
<h2><a class="anchor" id="group_prot_shared_memory_protection"></a>
Shared Memory Protection</h2>
<p>In order to protect a region of memory from all bus masters, an SMPU is used. This protection effectively allows only those with correct bus master access settings to read/write/execute the memory region. This type of protection is used in general memory such as Flash and SRAM. Peripheral registers are best configured using the peripheral protection units instead. SMPU structs have a descending priority, where larger index struct has higher priority access evaluation over lower index structs. E.g. SMPU_STRUCT15 has higher priority than SMPU_STRUCT14 and its access will be evaluated before SMPU_STRUCT14. If both target the same memory, then the higher index (MPU_STRUCT15) will be used, and the lower index (SMPU_STRUCT14) will be ignored.</p>
<h2><a class="anchor" id="group_prot_peripheral_protection"></a>
Peripheral Protection</h2>
<p>Peripheral protection is provided by PPUs and allow control of peripheral register accesses by bus masters. Four types of PPUs are available.</p><ul>
<li><b>Fixed Group (GR) PPUs</b> are used to protect an entire peripheral MMIO group from invalid bus master accesses. The MMIO grouping information and which resource belongs to which group is device specific and can be obtained from the device technical reference manual (TRM). Group PPUs have the highest priority in the PPU category. Therefore their access evaluations take precedence over the other types of PPUs.</li>
<li><b>Programmable (PROG) PPUs</b> are used to protect any peripheral memory region in a device from invalid bus master accesses. It is the most versatile type of peripheral protection unit. Programmable PPUs have the second highest priority and take precedence over Region PPUs and Slave PPUs. Similar to SMPUs, higher index PROG PPUs have higher priority than lower indexes PROG PPUs.</li>
<li><b>Fixed Region (RG) PPUs</b> are used to protect an entire peripheral slave instance from invalid bus master accesses. For example, TCPWM0, TCPWM1, SCB0, and SCB1, etc. Region PPUs have the third highest priority and take precedence over Slave PPUs.</li>
<li><b>Fixed Slave (SL) PPUs</b> are used to protect specified regions of peripheral instances. For example, individual DW channel structs, SMPU structs, and IPC structs, etc. Slave PPUs have the lowest priority in the PPU category and therefore are evaluated last.</li>
</ul>
<h1><a class="anchor" id="group_prot_protection_context"></a>
Protection Context</h1>
<p>Protection context (PC) attribute is present in all bus masters and is evaluated when accessing memory protected by an SMPU or a PPU. There are no limitations to how the PC values are allocated to the bus masters and this makes it possible for multiple bus masters to essentially share protection context values. The exception to this rule is the PC value 0.</p>
<h2><a class="anchor" id="group_prot_pc0"></a>
PC=0</h2>
<p>Protection context 0 is a hardware controlled protection context update mechanism that allows only a single entry point for transitioning into PC=0 value. This mechanism is only present for the secure CM0+ core and is a fundamental feature in defining a security solution. While all bus masters are configured to PC=0 at device boot, it is up to the security solution to transition these bus masters to PC!=0 values. Once this is done, those bus masters can no longer revert back to PC=0 and can no longer access resources protected at PC=0.</p>
<p>In order to enter PC=0, the CM0+ core must assign an interrupt vector or an exception handler address to the CPUSS.CM0_PC0_HANDLER register. This allows the hardware to check whether the executing code address matches the value in this register. If they match, the current PC value is saved and the CM0+ bus master automatically transitions to PC=0. It is then up to the executing code to decide if and when it will revert to a PC!=0 value. At that point, the only way to re-transition to PC=0 is through the defined exception/interrupt handler.</p>
<dl class="section note"><dt>Note</dt><dd>Devices with CPUSS ver_2 have a hardware-controlled protection context update mechanism that allows only a single-entry point for transitioning into PC=0, 1, 2, and 3. The interrupt vector or the exception handler address can be assigned to the CPUSS.CM0_PC0_HANDLER, CPUSS.CM0_PC1_HANDLER, CPUSS.CM0_PC2_HANDLER or CPUSS.CM0_PC2_HANDLER register. Also, the control register CPUSS.CM0_PC_CTL of the CM0+ protection context must be set: bit 0 - the valid field for CM0_PC0_HANDLER, bit 1 - the valid field for CM0_PC1_HANDLER, bit 2 - the valid field for CM0_PC2_HANDLER, and bit 3 - the valid field for CM0_PC3_HANDLER.</dd></dl>
<p>The example of using of the single entry point mechanism is shown below. </p><div class="fragment"><div class="line"><span class="comment">/* The code below demonstrates the protection context update </span></div><div class="line"><span class="comment"> * mechanism that allows a single entry point for transitioning </span></div><div class="line"><span class="comment"> * from PC = 1 into PC=0 value.</span></div><div class="line"><span class="comment"> */</span></div><div class="line">    </div><div class="line"><span class="comment">/* Note: &quot;cy_ipc_drv.h&quot;, &quot;cy_prot.h&quot; and &quot;cy_sysint.h&quot; should be included. */</span></div><div class="line"></div><div class="line"><span class="preprocessor">#if defined (CY_IP_M7CPUSS)</span></div><div class="line"><span class="preprocessor">#define IPC_INTR_NR 5u</span></div><div class="line"><span class="preprocessor">#else</span></div><div class="line"><span class="preprocessor">#define IPC_INTR_NR 10u</span></div><div class="line"><span class="preprocessor">#endif</span></div><div class="line"></div><div class="line">uint32_t pc; <span class="comment">/* The active protection context of a master. */</span></div><div class="line"><span class="keywordtype">bool</span> isrTriggered = <span class="keyword">false</span>; <span class="comment">/* The ISR flag. */</span></div><div class="line"></div><div class="line"><span class="comment">/* IPC ISR handler.  */</span></div><div class="line"><span class="keywordtype">void</span> isrPC0(<span class="keywordtype">void</span>)</div><div class="line">{</div><div class="line">    <span class="comment">/* The protection context is 0 here. */</span></div><div class="line">    </div><div class="line">    isrTriggered = <span class="keyword">true</span>; <span class="comment">/* Set flag that ISR is triggered. */</span></div><div class="line"></div><div class="line">    <a class="code" href="group__group__ipc__functions.html#ga408e08c5842189246a35ca2be89d62ea">Cy_IPC_Drv_ClearInterrupt</a>(<a class="code" href="group__group__ipc__functions.html#gaea293f27dc3d6d69eb40ef2d8f5c8d2b">Cy_IPC_Drv_GetIntrBaseAddr</a>(IPC_INTR_NR), 0u, 1u);</div><div class="line">}</div><div class="line"></div><div class="line"><span class="keywordtype">int</span> main(<span class="keywordtype">void</span>)</div><div class="line">{</div><div class="line">    __enable_irq(); <span class="comment">/* Enable global interrupts. */</span></div><div class="line"><span class="preprocessor">    #if (CY_CPU_CORTEX_M0P)</span></div><div class="line"><span class="preprocessor">    #if defined(CY_IP_M7CPUSS)</span></div><div class="line">        <span class="comment">/* Enable CM7. CY_CORTEX_M7_0_APPL_ADDR must be updated if CM7 memory layout is changed. */</span></div><div class="line">        <a class="code" href="group__group__system__config__cm7__functions.html#gacac741f6dd29eb66dc7e4fb31eef52fe">Cy_SysEnableCM7</a>(CORE_CM7_0, <a class="code" href="group__group__system__config__system__macro__cm7.html#gab9058603c83069bd2f36c01b1b77e90c">CY_CORTEX_M7_0_APPL_ADDR</a>);</div><div class="line"><span class="preprocessor">    #else</span></div><div class="line">        <span class="comment">/* Enable CM4. CY_CORTEX_M4_APPL_ADDR must be updated if CM4 memory layout is changed. */</span></div><div class="line">        <a class="code" href="group__group__system__config__cm4__functions.html#gac44c12fdb0562403fc055e4e8966b557">Cy_SysEnableCM4</a>(CY_CORTEX_M4_APPL_ADDR);</div><div class="line"><span class="preprocessor">    #endif</span></div><div class="line"><span class="preprocessor">    #endif</span></div><div class="line"></div><div class="line">    <span class="comment">/* Assign the isrPC0 interrupt vector to the CM0_PC0_HANDLER register. */</span></div><div class="line">    CPUSS-&gt;CM0_PC0_HANDLER = (uint32_t)&amp;isrPC0;</div><div class="line">    </div><div class="line">    <span class="comment">/* Configure the IPC interrupt handler. */</span></div><div class="line">    <a class="code" href="group__group__ipc__functions.html#ga741e9137775cdfab6275adaf45dd5406">Cy_IPC_Drv_SetInterruptMask</a>(<a class="code" href="group__group__ipc__functions.html#gaea293f27dc3d6d69eb40ef2d8f5c8d2b">Cy_IPC_Drv_GetIntrBaseAddr</a>(IPC_INTR_NR), 0u, 1u);</div><div class="line">    <a class="code" href="structcy__stc__sysint__t.html">cy_stc_sysint_t</a> intr = {</div><div class="line"><span class="preprocessor">        #if defined(CY_IP_M7CPUSS)</span></div><div class="line">            .<a class="code" href="structcy__stc__sysint__t.html#a204a8f07adf056c8d3dd818136da853f">intrSrc</a> = ((NvicMux5_IRQn &lt;&lt; <a class="code" href="group__group__sysint.html#ga3b9f1b9de4f122495a8b6580ce500d9a">CY_SYSINT_INTRSRC_MUXIRQ_SHIFT</a>) | cpuss_interrupts_ipc_5_IRQn),</div><div class="line"><span class="preprocessor">        #elif (CY_CPU_CORTEX_M0P)</span></div><div class="line">            .intrSrc = NvicMux5_IRQn,</div><div class="line">            .cm0pSrc = cpuss_interrupts_ipc_10_IRQn,</div><div class="line"><span class="preprocessor">        #else</span></div><div class="line">            .intrSrc = cpuss_interrupts_ipc_10_IRQn,</div><div class="line"><span class="preprocessor">        #endif </span><span class="comment">/* (CY_CPU_CORTEX_M0P) */</span><span class="preprocessor"></span></div><div class="line">        .intrPriority = 2u</div><div class="line">    };</div><div class="line">    <a class="code" href="group__group__sysint__functions.html#gab2ff6820a898e9af3f780000054eea5d">Cy_SysInt_Init</a>(&amp;intr, isrPC0);</div><div class="line">    NVIC_EnableIRQ(intr.<a class="code" href="structcy__stc__sysint__t.html#a204a8f07adf056c8d3dd818136da853f">intrSrc</a>);</div><div class="line"></div><div class="line">    <span class="comment">/* Configure the bus master to allow setting PC to PC=1 and PC=2 */</span></div><div class="line">    <a class="code" href="group__group__prot__functions__busmaster.html#ga4b69f79e24b30f22a706e973b05dd079">Cy_Prot_ConfigBusMaster</a>(CPUSS_MS_ID_CM0, <span class="keyword">true</span>, <span class="keyword">true</span>, <a class="code" href="group__group__prot__enums.html#gga4486bc74d6e98ad99c1ce4d532e48d0fabf25e25bbce833636da932ce78e453e8">CY_PROT_PCMASK1</a> | <a class="code" href="group__group__prot__enums.html#gga4486bc74d6e98ad99c1ce4d532e48d0fa0b17d740a164ae90f06a4ab2f17d79d0">CY_PROT_PCMASK2</a>);</div><div class="line"></div><div class="line">    <span class="comment">/* Set the CM0+ PC value to 1 */</span></div><div class="line">    <span class="keywordflow">if</span>(<a class="code" href="group__group__prot__enums.html#gga13ede85383a4afaf5ed3a14b470e38bda462f07fcb31ed8a07dd273af4290691d">CY_PROT_SUCCESS</a> != <a class="code" href="group__group__prot__functions__busmaster.html#ga2d3a54039578a9fae98f6c7b4c4cff41">Cy_Prot_SetActivePC</a>(CPUSS_MS_ID_CM0, <a class="code" href="group__group__prot__enums.html#gga4467b93f3da4304e584726b975d3fabaa10dc15f2738ba076ded84cb7b9eac7fa">CY_PROT_PC1</a>))</div><div class="line">    {</div><div class="line">        <span class="comment">/* Insert error handling */</span></div><div class="line">    }</div><div class="line"></div><div class="line">    pc = <a class="code" href="group__group__prot__functions__busmaster.html#gac6af4217bc8ac5517edb39ebe11e91ec">Cy_Prot_GetActivePC</a>(CPUSS_MS_ID_CM0); <span class="comment">/* pc should equal to 1 */</span></div><div class="line"></div><div class="line">    <a class="code" href="group__group__ipc__functions.html#ga5fb9bd90c225d8cc4bc8c9ef1a829948">Cy_IPC_Drv_SetInterrupt</a>(<a class="code" href="group__group__ipc__functions.html#gaea293f27dc3d6d69eb40ef2d8f5c8d2b">Cy_IPC_Drv_GetIntrBaseAddr</a>(IPC_INTR_NR), 0u, 1u); <span class="comment">/* Trigger the ISR */</span></div><div class="line">  </div><div class="line">    <span class="keywordflow">while</span>(!isrTriggered)</div><div class="line">    {</div><div class="line">        <span class="comment">/* Wait until isrPC0 ISR entered. */</span></div><div class="line">    }</div><div class="line">    </div><div class="line">    pc = <a class="code" href="group__group__prot__functions__busmaster.html#gac6af4217bc8ac5517edb39ebe11e91ec">Cy_Prot_GetActivePC</a>(CPUSS_MS_ID_CM0); <span class="comment">/* pc should equal to 0 */</span></div><div class="line"></div><div class="line">    <span class="keywordflow">for</span>(;;)</div><div class="line">    {</div><div class="line"></div><div class="line">    }</div><div class="line">}</div></div><!-- fragment --> <h1><a class="anchor" id="group_prot_access_evaluation"></a>
Access Evaluation</h1>
<p>Each protection unit is capable of evaluating several access types. These can be used to build a system of logical evaluations for different kinds of bus master modes of operations. These access types can be divided into three broad access categories.</p>
<ul>
<li><b>User/Privileged access:</b> The ARM convention of user mode versus privileged mode is applied in the protection units. For ARM cores, switching between user and privileged modes is handled by updating its Control register or by exception entries. Other bus masters such as Crypto have their own user/privileged settings bit in the bus master control register. This is then controlled by the ARM cores. Bus masters that do not have user/privileged access controls, such as DMA, inherit their attributes from the bus master that configured it. The user/privileged distinction is used mainly in the MPUs for single bus master accesses but they can also be used in all other protection units.</li>
<li><b>Secure/Non-secure access:</b> The secure/non-secure attribute is another identifier to distinguish between two separate modes of operations. Much like the user/privileged access, the secure/non-secure mode flag is present in the bus master control register. The ARM core does not have this attribute in its control register and must use the bus master control register instead. Bus masters that inherit their attributes, such as DMA, inherit the secure/non-secure attribute. The primary use-case for this access evaluation is to define a region to be secure or non-secure using an SMPU or a PPU. A bus master with a secure attribute can access both secure and non-secure regions, whereas a bus master with non-secure attribute can only access non-secure regions.</li>
<li><b>Protection Context access:</b> Protection Context is an attribute that serves two purposes; To enter the hardware controlled secure PC=0 mode of operation from non-secure modes and to provide finer granularity to the bus master access definitions. It is used in SMPU and PPU configuration to control which bus master protection context can access the resources that they protect.</li>
</ul>
<h1><a class="anchor" id="group_prot_protection_structure"></a>
Protection Structure</h1>
<p>Each protection unit is comprised of a master struct and a slave struct pair. The exception to this rule is MPU structs, which only have the slave struct equivalent. The protection units apply their access evaluations in a decreasing index order. For example, if SMPU1 and SMPU2 both protect a specific memory region, the the higher index (SMPU2) will be evaluated first. In a secure system, the higher index protection structs would then provide the high level of security and the lower indexes would provide the lower level of security. Refer to the <a class="el" href="group__group__prot.html#group_prot_protection_type">Protection Types</a> section for more information.</p>
<h2><a class="anchor" id="group_prot_slave_struct"></a>
Slave Struct</h2>
<p>The slave struct is used to configure the protection settings for the resource of interest (memory/registers). Depending on the type of protection unit, the available attributes differ. However all Slave protection units have the following general format.</p>
<h3><a class="anchor" id="group_prot_slave_addr"></a>
Slave Struct Address Definition</h3>
<ul>
<li>Address: For MPU, SMPU and PROG PPU, the address field is used to define the base memory region to apply the protection. This field has a dependency on the region size, which dictates the alignment of the protection unit. E.g. if the region size is 64KB, the address field is aligned to 64KB. Hence the lowest bits [15:0] are ignored. For instance, if the address is defined at 0x0800FFFF, the protection unit would apply its protection settings from 0x08000000. Thus alignment must be checked before defining the protection address. The address field for other PPUs are not used, as they are bound to their respective peripheral memory locations.</li>
<li>Region Size: For MPU, SMPU and PROG PPU, the region size is used to define the memory block size to apply the protection settings, starting from the defined base address. It is also used to define the 8 sub-regions for the chosen memory block. E.g. If the region size is 64KB, each subregion would be 8KB. This information can then be used to disable the protection settings for select subregions, which gives finer granularity to the memory regions. PPUs do not have region size definitions as they are bound to their respective peripheral memory locations.</li>
<li>Subregions: The memory block defined by the address and region size fields is divided into 8 (0 to 7) equally spaced subregions. The protection settings of the protection unit can be disabled for these subregions. E.g. for a given 64KB of memory block starting from address 0x08000000, disabling subregion 0 would result in the protection settings not affecting the memory located between 0x08000000 to 0x08001FFF. PPUs do not have subregion definitions as they are bound to their respective peripheral memory locations.</li>
</ul>
<h3><a class="anchor" id="group_prot_slave_attr"></a>
Slave Struct Attribute Definition</h3>
<ul>
<li>User Permission: Protection units can control the access restrictions of the read (R), write (W) and execute (X) (subject to their availability depending on the type of protection unit) operations on the memory block when the bus master is operating in user mode. PPU structs do not provide execute attributes.</li>
<li>Privileged Permission: Similar to the user permission, protection units can control the access restrictions of the read (R), write (W) and execute (X) (subject to their availability depending on the type of protection unit) operations on the memory block when the bus master is operating in privileged mode. PPU structs do not provide execute attributes.</li>
<li>Secure/Non-secure: Applies the secure/non-secure protection settings to the defined memory region. Secure protection allows only bus masters that access the memory with secure attribute. Non-secure protection allows bus masters that have either secure or non-secure attributes.</li>
<li>PC match: This attribute allows the protection unit to either apply the 3 access evaluations (user/privileged, secure/non-secure, protection context) or to only provide an address range match. This is useful when multiple protection units protect an overlapping memory region and it's desirable to only have access evaluations applied from only one of these protection units. For example, SMPU1 protects memory A and SMPU2 protects memory B. There exists a region where A and B intersect and this is accessed by a bus master. Both SMPU1 and SMPU2 are configured to operate in "match" mode. In this scenario, the access evaluation will only be applied by the higher index protection unit (i.e. SMPU2) and the access attributes of SMPU1 will be ignored. If the bus master then tries to access a memory region A (that does not intersect with B), the access evaluation from SMPU1 will be used. Note that the PC match functionality is only available in SMPUs.</li>
<li>PC mask: Defines the allowed protection context values that can access the protected memory. The bus master attribute must be operating in one of the protection context values allowed by the protection unit. E.g. If SMPU1 is configured to allow only PC=1 and PC=5, a bus master (such as CM4) must be operating at PC=1 or PC=5 when accessing the protected memory region.</li>
</ul>
<h2><a class="anchor" id="group_prot_master_struct"></a>
Master Struct</h2>
<p>The master struct protects its slave struct in the protection unit. This architecture makes possible for the slave configuration to be protected from reconfiguration by an unauthorized bus master. The configuration attributes and the format are similar to that of the slave structs.</p>
<h3><a class="anchor" id="group_prot_master_addr"></a>
Master Struct Address Definition</h3>
<ul>
<li>Address: The address definition for master struct is fixed to the slave struct that it protects.</li>
<li>Region Size: The region size is fixed to 256B region.</li>
<li>Subregion: This value is fixed to only enable the first 64B subregions, which applies the protection settings to the entire protection unit.</li>
</ul>
<h3><a class="anchor" id="group_prot_master_attr"></a>
Master Struct Attribute Definition</h3>
<ul>
<li>User Permission: Only the write (W) access attribute is allowed for master structs, which controls whether a bus master operating in user mode has the write access.</li>
<li>Privileged Permission: Only the write (W) access attribute is allowed for master structs, which controls whether a bus master operating in privileged mode has the write access.</li>
<li>Secure/Non-Secure: Same behavior as slave struct.</li>
<li>PC match: Same behavior as slave struct.</li>
<li>PC mask: Same behavior as slave struct.</li>
</ul>
<h1><a class="anchor" id="group_prot_driver_usage"></a>
Driver Usage</h1>
<p>Setting up and using protection units can be summed up in four stages:</p>
<ul>
<li>Configure the bus master attributes. This defines the capabilities of the bus master when trying to access the protected resources.</li>
<li>Configure the slave struct of a given protection unit. This defines the protection attributes to be applied to the bus master accessing the protected resource and also defines the size and location of the memory block to protect.</li>
<li>Configure the master struct of the protection unit. This defines the attributes to be checked against the bus master that is trying to reconfigure the slave struct.</li>
<li>Set the active PC value of the bus master and place it in the correct mode of operation (user/privileged, secure/non-secure). Then access the protected memory.</li>
</ul>
<p>For example, by configuring the CM0+ bus master configuration to allow only protection contexts 2 and 3, the bus master will be able to set its protection context only to 2 or 3. During runtime, the CM0+ core can set its protection context to 2 by calling <a class="el" href="group__group__prot__functions__busmaster.html#ga2d3a54039578a9fae98f6c7b4c4cff41" title="Sets the current/active protection context of the specified bus master. ">Cy_Prot_SetActivePC()</a> and access all regions of protected memory that allow PC=2. A fault will be triggered if a resource is protected with different protection settings.</p>
<p>Note that each protection unit is distinguished by its type (e.g. <a class="el" href="struct_p_r_o_t___m_p_u___m_p_u___s_t_r_u_c_t___type.html" title="The struct type definition for the hardware register set contained in the block.  The address of a va...">PROT_MPU_MPU_STRUCT_Type</a>). The list of supported protection units can be obtained from the device definition header file. Choose a protection unit of interest, and call its corresponding Cy_Prot_Config&lt;X&gt;Struct() function with its software protection unit configuration structure populated. Then enable the protection unit by calling the Cy_Prot_Enable&lt;X&gt;Struct() function.</p>
<p>Note that the bus master ID (en_prot_master_t) is defined in the device config header file.</p>
<h1><a class="anchor" id="group_prot_configuration"></a>
Configuration Considerations</h1>
<p>When a resource (memory/register) is accessed, it must pass evaluation of all three protection unit categories in the following order: MPU-&gt;SMPU-&gt;PPU. The application should ensure that a denial-of-service attack cannot be made on the PPU by the SMPU. For this reason, it is recommended that the application's security policy limit the ability for the non-secure client from configuring the SMPUs.</p>
<p>Within each category, the priority hierarchy must be carefully considered to ensure that a higher priority protection unit cannot be configured to override the security configuration of a lower index protection unit. Therefore if a lower index protection unit is configured, relevant higher priority indexes should be configured (or protected from unwanted reconfiguration). E.g. If a PPU_SL is configured, PPU_RG and PPU_GR that overlaps with the protected registers should also be configured. SImilar to SMPUs, it is recommended that the configuration of PPU_PROG be limited. Otherwise they can be used to override the protection settings of PPU_RG and PPU_SL structs.</p>
<p>All bus masters are set to PC=0 value at device reset and therefore have full access to all resources. It is up to the security solution to implement what privileges each bus master has. Once transitioned to a PC!=0 value, only the CM0+ core is capable of re-entering the PC=0 via the user-defined exception entry in the CPUSS.CM0_PC0_HANDLER register.</p>
<ul>
<li>SMPU 15 and 14 are configured and enabled to only allow PC=0 accesses at device boot.</li>
<li>PROG PPU 15, 14, 13 and 12 are configured to only allow PC=0 accesses at device boot.</li>
<li>GR PPU 0 and 2 are configured to only allow PC=0 accesses at device boot.</li>
</ul>
<h1><a class="anchor" id="group_prot_more_information"></a>
More Information</h1>
<p>Refer to Technical Reference Manual (TRM) and the device datasheet.</p>
<h1><a class="anchor" id="group_prot_changelog"></a>
Changelog</h1>
<table class="doxtable">
<tr>
<th>Version</th><th>Changes</th><th>Reason for Change </th></tr>
<tr>
<td>1.100 </td><td>Updating implementation of internal function that configures attributes. </td><td>Defect fix.  </td></tr>
<tr>
<td>1.90 </td><td>Added support for TRAVEO&trade; II Body Entry devices.<br />
 Updated conditions in pre-processor check for if the device has a CM4 to also check for for MXPERI ver. 1.<br />
 Cleaned up redundant code.<br />
 Bug fix: Updates some API availability based on the PERI version. Some devices may have a reduced set of functions available. If code called APIs not appropriate for the version of PERI, that code will not build without updating to reflect new API availability. Please note, however, that if code was calling those APIs and the functions are no longer available, there will be no functional difference as the calls were available before but did nothing if the device hardware didn't support the function. This change makes the API accurately reflect hardware capability. </td><td>Code enhancement and support for new devices.  </td></tr>
<tr>
<td>1.80 </td><td><a class="el" href="group__group__prot__functions__ppu__prog__v2.html#ga37f73e968bc327a33ae55eab02c315ac">Cy_Prot_ConfigPpuProgSlaveAddr()</a>, <a class="el" href="group__group__prot__functions__ppu__prog__v2.html#ga93cd67a67fecfb39b3df272b9f64a780">Cy_Prot_EnablePpuProgSlaveRegion()</a> <a class="el" href="group__group__prot__functions__ppu__prog__v2.html#gacd5db7ab07edb2943e6f0c2486c6c6d0">Cy_Prot_DisablePpuProgSlaveRegion()</a> APIs are only available for PSoC6 devices </td><td>MISRA C-2012 compliance and Move PERI version-1 APIs to supported devices  </td></tr>
<tr>
<td>1.70 </td><td>Added support for CAT1C devices.  </td><td>New device added.   </td></tr>
<tr>
<td>1.60 </td><td>Modified <a class="el" href="group__group__prot__functions__ppu__prog__v2.html#gaa20aec5caa83d665c5a2afe241b6c69e">Cy_Prot_ConfigPpuProgMasterAtt()</a> &amp; <a class="el" href="group__group__prot__functions__ppu__fixed__v2.html#gacc7dadd726bd53886aedfbfa1014ae9e">Cy_Prot_ConfigPpuFixedMasterAtt()</a> functions to ignore unavailable protection context. </td><td>Defect fix.  </td></tr>
<tr>
<td rowspan="3">1.50 </td><td>Updated implementation of the <a class="el" href="group__group__prot__functions__ppu__prog__v2.html#gaa20aec5caa83d665c5a2afe241b6c69e">Cy_Prot_ConfigPpuProgMasterAtt()</a>, <a class="el" href="group__group__prot__functions__ppu__prog__v2.html#ga7941e969542970aedcb056f554b5383b">Cy_Prot_ConfigPpuProgSlaveAtt()</a>, <a class="el" href="group__group__prot__functions__ppu__fixed__v2.html#gacc7dadd726bd53886aedfbfa1014ae9e">Cy_Prot_ConfigPpuFixedMasterAtt()</a>, and <a class="el" href="group__group__prot__functions__ppu__fixed__v2.html#ga6112f6eba93e5db763e8dc571a91740a">Cy_Prot_ConfigPpuFixedSlaveAtt()</a> to start registers update from the higher-numbered PCs in order to prevent lockup for the case when registers are configured to read-only. </td><td>Defect fix.  </td></tr>
<tr>
<td>Added macros for memory region size setting in <a class="el" href="group__group__prot__enums.html#gaad39ed0d259460f717edfe9d08fc005f">cy_en_prot_size_t</a> initialization. </td><td>The macros can be useful for the pre-processor checks.  </td></tr>
<tr>
<td>Fixed/Documented MISRA 2012 violations. </td><td>MISRA 2012 compliance.  </td></tr>
<tr>
<td>1.40 </td><td><ul>
<li>Updated the <a class="el" href="group__group__prot__functions__busmaster.html#ga2d3a54039578a9fae98f6c7b4c4cff41">Cy_Prot_SetActivePC()</a> function to report an error when called on the secure CYB06xx7 devices as no access privileges are available.</li>
<li>Updated the <a class="el" href="group__group__prot__functions__busmaster.html#gac6af4217bc8ac5517edb39ebe11e91ec">Cy_Prot_GetActivePC()</a> function for the secure CYB06xx7 devices to access the protected registers via the <a class="el" href="group__group__pra.html">PRA (Protected Register Access)</a> driver.  </li>
</ul>
</td><td>Added PSoC 64 devices support.  </td></tr>
<tr>
<td>1.30.3 </td><td>Minor documentation updates. </td><td>Documentation enhancement.  </td></tr>
<tr>
<td>1.30.2 </td><td>Clarified the description of the next API functions: <a class="el" href="group__group__prot__functions__ppu__prog__v2.html#gaa20aec5caa83d665c5a2afe241b6c69e">Cy_Prot_ConfigPpuProgMasterAtt</a>,<br />
 <a class="el" href="group__group__prot__functions__ppu__prog__v2.html#ga7941e969542970aedcb056f554b5383b">Cy_Prot_ConfigPpuProgSlaveAtt</a>, <a class="el" href="group__group__prot__functions__ppu__fixed__v2.html#gacc7dadd726bd53886aedfbfa1014ae9e">Cy_Prot_ConfigPpuFixedMasterAtt</a>, <a class="el" href="group__group__prot__functions__ppu__fixed__v2.html#ga6112f6eba93e5db763e8dc571a91740a">Cy_Prot_ConfigPpuFixedSlaveAtt</a>. </td><td>API enhancement based on usability feedback.  </td></tr>
<tr>
<td>1.30.1 </td><td>Snippet updated. </td><td>Old snippet outdated.  </td></tr>
<tr>
<td>1.30 </td><td>Defect in <a class="el" href="group__group__prot__functions__ppu__prog.html#gaea671baa8df5f37922e7325a291e250c">Cy_Prot_GetPpuProgStruct()</a> function due to faulty defines is fixed. </td><td>Defect fixing.  </td></tr>
<tr>
<td rowspan="3">1.20 </td><td>Flattened the organization of the driver source code into the single source directory and the single include directory. </td><td>Driver library directory-structure simplification.  </td></tr>
<tr>
<td>Added functions for CPUSS ver_2:<ul>
<li><a class="el" href="group__group__prot__functions__ppu__prog__v2.html#gaa20aec5caa83d665c5a2afe241b6c69e">Cy_Prot_ConfigPpuProgMasterAtt()</a></li>
<li><a class="el" href="group__group__prot__functions__ppu__prog__v2.html#ga37f73e968bc327a33ae55eab02c315ac">Cy_Prot_ConfigPpuProgSlaveAddr()</a></li>
<li><a class="el" href="group__group__prot__functions__ppu__prog__v2.html#ga7941e969542970aedcb056f554b5383b">Cy_Prot_ConfigPpuProgSlaveAtt()</a></li>
<li><a class="el" href="group__group__prot__functions__ppu__prog__v2.html#ga93cd67a67fecfb39b3df272b9f64a780">Cy_Prot_EnablePpuProgSlaveRegion()</a></li>
<li><a class="el" href="group__group__prot__functions__ppu__prog__v2.html#gacd5db7ab07edb2943e6f0c2486c6c6d0">Cy_Prot_DisablePpuProgSlaveRegion()</a></li>
<li><a class="el" href="group__group__prot__functions__ppu__fixed__v2.html#gacc7dadd726bd53886aedfbfa1014ae9e">Cy_Prot_ConfigPpuFixedMasterAtt()</a></li>
<li><a class="el" href="group__group__prot__functions__ppu__fixed__v2.html#ga6112f6eba93e5db763e8dc571a91740a">Cy_Prot_ConfigPpuFixedSlaveAtt()</a>  </li>
</ul>
</td><td>Added support for CPUSS ver_2.  </td></tr>
<tr>
<td>Added register access layer. Use register access macros instead of direct register access using dereferenced pointers. </td><td>Makes register access device-independent, so that the PDL does not need to be recompiled for each supported part number.  </td></tr>
<tr>
<td rowspan="2">1.10 </td><td>Added input parameter validation to the API functions.<br />
 cy_en_prot_pcmask_t, cy_en_prot_subreg_t and cy_en_prot_pc_t types are set to typedef enum </td><td>Improved debugging capability  </td></tr>
<tr>
<td>Expanded documentation </td><td></td></tr>
<tr>
<td>1.0 </td><td>Initial version </td><td></td></tr>
</table>
<table class="memberdecls">
<tr class="heading"><td colspan="2"><h2 class="groupheader"><a name="groups"></a>
API Reference</h2></td></tr>
<tr class="memitem:group__group__prot__macros"><td class="memItemLeft" align="right" valign="top">&#160;</td><td class="memItemRight" valign="bottom"><a class="el" href="group__group__prot__macros.html">Macros</a></td></tr>
<tr class="separator:"><td class="memSeparator" colspan="2">&#160;</td></tr>
<tr class="memitem:group__group__prot__functions"><td class="memItemLeft" align="right" valign="top">&#160;</td><td class="memItemRight" valign="bottom"><a class="el" href="group__group__prot__functions.html">Functions</a></td></tr>
<tr class="separator:"><td class="memSeparator" colspan="2">&#160;</td></tr>
<tr class="memitem:group__group__prot__data__structures"><td class="memItemLeft" align="right" valign="top">&#160;</td><td class="memItemRight" valign="bottom"><a class="el" href="group__group__prot__data__structures.html">Data Structures</a></td></tr>
<tr class="separator:"><td class="memSeparator" colspan="2">&#160;</td></tr>
<tr class="memitem:group__group__prot__enums"><td class="memItemLeft" align="right" valign="top">&#160;</td><td class="memItemRight" valign="bottom"><a class="el" href="group__group__prot__enums.html">Enumerated Types</a></td></tr>
<tr class="separator:"><td class="memSeparator" colspan="2">&#160;</td></tr>
</table>
</div><!-- contents -->
</div><!-- doc-content -->
<!-- start footer part
<div id="nav-path" class="navpath">
    <ul>
        <li class="footer">
            Generated for <b>MTB CAT1 Peripheral driver library</b> by <b>Cypress Semiconductor Corporation</b>.
            All rights reserved.
        </li>
    </ul>
</div>
-->
</body>
</html>
